function postfixEval(postfixArr)
{
	var stack = new Stack();
	for (var x in postfixArr)
	{	
		var token = postfixArr[x];
		if (isOperand(token))
		{
			stack.push(token);
		}
		else if (token == '+')
		{
			var secondArg = stack.pop();
			var firstArg = stack.pop();
			stack.push((firstArg - 0) + (secondArg - 0));
		}
		else if (token == '-')
		{
			var secondArg = stack.pop();
			var firstArg = stack.pop();
			stack.push((firstArg - 0) - (secondArg - 0));
		}
		else if (token == 'x')
		{
			var secondArg = stack.pop();
			var firstArg = stack.pop();
			stack.push((firstArg - 0) * (secondArg - 0));
		}
		else if (token == '/')
		{
			// + - x /
			var secondArg = stack.pop();
			var firstArg = stack.pop();
			if (secondArg == '0')
			{
				throw new Error('Math ERROR');
			}
			else
			{
				stack.push((firstArg - 0) / (secondArg - 0));
			}
		}
		else if (token == 'sin' || token == 'cos')
		{
			var arg = stack.pop();
			stack.push(Math[token]((arg - 0) * Math.PI / 180));
		}
		else if (token == 'tan')
		{
			// Degree
			var arg = stack.pop();
			if (((arg - 0) % 90) == 1)
			{
				throw new Error('Math ERROR');
			}
			else
			{
				stack.push(Math.tan((arg - 0) * Math.PI / 180));
			}
			
		}
		else if (token == 'cot')
		{
			var arg = stack.pop();
			if ((arg - 0) % 180 == 0)
			{
				throw new Error('Math ERROR');
			}
			else
			{
				var radVal = (arg - 0) * Math.PI / 180;
				stack.push(Math.cos(radVal) / Math.sin(radVal));
			}
		}
		else if (token == 'log')
		{
			var arg = stack.pop();
			var base = stack.pop();
			if (base == 1 || (arg - 0) <= 0 || (base - 0) <= 0)
			{
				throw new Error('Math ERROR');
			}
			else
			{
				stack.push(Math.log(arg - 0) / Math.log(base - 0));
			}
		}
		else if (token == 'ln')
		{
			var arg = stack.pop();
			if ((arg - 0) <= 0)
			{
				throw new Error('Math ERROR');
			}
			else
			{
				stack.push(Math.log(arg - 0));
			}
		}
		else if (token == '^')
		{
			var secondArg = stack.pop();
			var firstArg = stack.pop();
			stack.push(power((firstArg - 0), (secondArg - 0)));
			
		}
		else if (token == 'v')
		{
			var firstArg = stack.pop();
			var secondArg = stack.pop();
			stack.push(root(firstArg - 0, secondArg - 0));
		}
		// else if (token == 'inv')
		// {
			// var arg = stack.pop();
			// stack.push(-(arg - 0));
		// }
	}
	return stack.pop();
}

function evaluate(ex)
{	
	console.log(ex);
	var result = 0;
	var temp;
	if (ex == '')
	{
		result = 0;
	}
	else
	{
		if (typeof(ex) == 'string')
		{
			temp =ex;
		}
		else
		{
			checkSyntaxError(ex);
			var temp = '';
			for (var i = 0; i < ex.length; i++)
			{
				temp += ex[i];
			}
		}
		result = postfixEval(infix2postfix(temp));
	}
	if (0 < result && result < Math.pow(10, -14))
	{
		result = 0;
	}
	return result;
}

function checkSyntaxError(ex)
{
	var num = 0;
	for (var token in ex)
	{
		if (('' + ex[token]).indexOf('(') != -1)
		{
			num++;
		}
		if (('' + ex[token]).indexOf(')') != -1)
		{
			num--;
		}
	}
	if (num != 0)
	{
		throw new Error('Syntax error');
	}
}
